#pragma once

#include "core/logger.h"
#include "core/event.h"
#include "core/config.h"
#include "core/kernel.h"

#include "video/video.h"
#include "input/input.h"

#include "app/application.h"

namespace natrium {
	namespace core {
		class Engine {
		public:
			typedef std::map<std::string, std::unique_ptr<System>> SystemMap; //owning, unique pointers. The Engine takes care of systems' lifetimes.

			Engine();
			virtual ~Engine();

			bool add(std::unique_ptr<System>&& s);
			bool remove(System* s);

			System* get(const std::string& name) const;

			void run();
			void stop();

			void setApplication(std::unique_ptr<app::Application>&& app);
			const app::Application* application();

			EventChannel& events();

		private:
			void initializeSystems();
			void shutdownSystems();

			SystemMap mSystemMap;
			Kernel mKernel;
			EventChannel mChan;

			std::unique_ptr<app::Application> mApplication;
			std::unique_ptr<Config> mConfig;
		};
	}
}